﻿using System;
using System.Collections;
using System.Collections.Generic;
using System.Linq;
using System.Threading.Tasks;
using Zzcore.Model;
using FreeSql;
using FreeSql.Internal.Model;
using Microsoft.AspNetCore.Http;
using Microsoft.AspNetCore.Mvc;
using Microsoft.Extensions.Logging;
using Newtonsoft.Json;
using Newtonsoft.Json.Linq;

namespace Zzcore.Controllers
{
    public class AdminController : BaseController
    {
        private readonly ILogger<AdminController> _logger;
        public AdminController(ILogger<AdminController> logger, IFreeSql fsql) : base(fsql)
        {
            this._logger = logger;
        }

        [HttpPost]
        public async Task<IDictionary<string, Object>> Index([FromForm] long did, [FromForm] string content, [FromForm] int pageNumber = 1, [FromForm] int pageSize = 10)
        {
            List<User> users = await _fsql.Select<User>().Count(out var total).WhereIf(!string.IsNullOrEmpty(content), u => u.Realname.Contains(content) || u.Phone.Contains(content) || u.Username.Contains(content) || u.WorkNumber.Contains(content)).WhereIf(did != 0, u => u.Did == did).Page(pageNumber, pageSize).ToListAsync();
            _logger.LogInformation("用户列表SQL：" + _fsql.Select<User>().WhereIf(!string.IsNullOrEmpty(content), u => u.Realname.Contains(content) || u.Phone.Contains(content) || u.Username.Contains(content) || u.WorkNumber.Contains(content)).WhereIf(did != 0, u => u.Did == did).ToSql());
            JObject jo_data = new();
            jo_data.Add("total", total);
            JArray ja_users = new();
            foreach (User user in users)
            {
                user.Rids = await _fsql.Select<RoleUser>().Where(ru => ru.Uid == user.Id).ToListAsync(ru => ru.Rid);
                JObject jo_user = JObject.FromObject(user);

                Department department = await _fsql.Select<Department>().Where(d => d.Id == user.Did).ToOneAsync();
                jo_user.Add("department", department == null ? null : JObject.FromObject(department));

                ja_users.Add(jo_user);
            }
            jo_data.Add("list", ja_users);
            return RenderJson(data: jo_data);
        }

        [HttpPost]
        public async Task<IDictionary<string, Object>> Save([FromForm] User user)
        {
            // 判断用户是否存在
            User isExistsUser = await _fsql.Select<User>().Where(u => u.Username == user.Username).ToOneAsync();
            if (isExistsUser != null)
            {
                return RenderJson(status: "失败", message: "该用户已经存在", code: -1);
            }

            long id = await _fsql.Insert<User>(user).ExecuteIdentityAsync();
            user.Id = id;

            if (user.Rids?.Count > 0)
            {
                // 先清空该角色所有用户
                await _fsql.Delete<RoleUser>().Where(u => u.Uid == id).ExecuteAffrowsAsync();

                List<RoleUser> roleusers = new();
                foreach (long rid in user.Rids)
                {
                    roleusers.Add(new RoleUser { Rid = rid, Uid = id });
                }
                int affrows = await _fsql.Insert<RoleUser>(roleusers).ExecuteAffrowsAsync();
            }

            return RenderJson(data: user);
        }

        [HttpPost]
        public async Task<IDictionary<string, Object>> Delete([FromForm] long id) {
            User user = await _fsql.Select<User>().Where(u => u.Id == id).ToOneAsync();
            if (user.Username.Equals("admin")) {
                return RenderJson(status: "failed", message: "管理员无法删除", code: -1, data: user);
            }
            int affrows = await _fsql.Delete<User>().Where(u => u.Id == id).ExecuteAffrowsAsync();
            return RenderJson(data: affrows);
        }

        [HttpPost]
        public async Task<IDictionary<string, Object>> Update([FromForm] User user) {
            int affrows = await _fsql.Update<User>().SetSource(user).ExecuteAffrowsAsync();

            if (user.Rids?.Count > 0)
            {
                // 先清空该角色所有用户
                await _fsql.Delete<RoleUser>().Where(u => u.Uid == user.Id).ExecuteAffrowsAsync();

                List<RoleUser> roleusers = new();
                foreach (long rid in user.Rids)
                {
                    roleusers.Add(new RoleUser { Rid = rid, Uid = user.Id });
                }
                await _fsql.Insert<RoleUser>(roleusers).ExecuteAffrowsAsync();
            }

            return RenderJson(data: affrows);
        }

        [HttpPost]
        public async Task<IDictionary<string, Object>> Show([FromForm] long id) {
            User user = await _fsql.Select<User>().Where(u => u.Id == id).ToOneAsync();

            user.Rids = await _fsql.Select<RoleUser>().Where(ru => ru.Uid == user.Id).ToListAsync(ru => ru.Rid);
            JObject data = JObject.FromObject(user);

            Department department = await _fsql.Select<Department>().Where(d => d.Id == user.Did).ToOneAsync();
            data.Add("department", department == null ? null : JObject.FromObject(department));

            return RenderJson(data: data);
        }
    }
}
